﻿using System;

/* 
 * 创建人：Kewin
 * 
 * 时间：2010.6-2010.9
 * 
 * 说明：
 * 
 * 
 * 修改说明：
 * 
 * 
 */


namespace ConsoleTest.ChapterEleven
{
    /// <summary>
    /// 
    /// </summary>
    public class Class
    {
        /*类中应当避免循环的引用，
         * 因为这样的错误编译器无法检测，直到栈或者堆发生溢出
         */

        /*ref
         * C#默认按值传递值类型参数，按引用传递引用类型参数。
         * 如果需要按引用传递值类型参数，那么可以在形参和实参前加ref关键字。
         * 
         * 按引用传递引用类型参数允许被调方法直接操作引用，
         * 即被调方法可以直接修改主调方法引用锁引用的对象。
         */

        /*ref out
         * ref指示参数以引用方式进行传递，参数在传递给方法之前
         * 值类型的必须对其进行初始化，引用类型的必须进行初始化或者设置为null值。
         * 
         * out指示该参数将作为一个返回值，out指示的参数不需要（可以不初始化）在被调方法
         * 内部进行初始化。
         */

        /*参数个数params 与默认值
         * 
         * C#不允许方法参数有默认值，可以使用方法重载的方式来解决，代价要大。
         * C#使用params关键字指示方法具有不定数目参数，params关键字的参数必须为方法
         * 的最后一个参数。
         * 使用params关键字的参数要对应object类型，因为它是所有类型的基类。
         */

        /*嵌套类型
         * 定义在别的类型内部的类型被称为嵌套类型。
         * 嵌套类型不允许在声明它的类以外的代码中使用。
         * 嵌套类型可以访问包含它的类型的所有成员
         */

        /*封装与可见性
         * 
         * 类的成员包括字段、属性、方法、事件、索引器以及内嵌类型
         * 如果没有指定可见性关键字（private/public/protected/internal）成员在
         * 类和结构中都默认声明为private
         */

        /*Dispose方法与终结器
         * 
         * C#中使用类似于C++中析构函数的方法为类定义终结器，该方法有垃圾回收器调用。
         * 另外可以实现IDisposable接口，复写Dispose方法，这样可以由类的使用者进行调用
         * 不过该方法不会改变垃圾回收器的行为。
         * 另外使用using关键字可以隐式的创建一个try/finally块，在finally自动调用Dispose方法。
         * （可见：能够使用using形式的类必须实现IDisposable接口）
         * 另外在对象的Dispose方法中最好引发System.ObjectDisposedException异常以阻止对象其他方法的调用
         * 
         * 多线程应用中可能出现Dispose方法多次调用的问题，这就需要考虑Dispose方法中的资源同步问题。
         * 
         * 
         */

        /*静态
         * 1、静态方法
         * 静态方法无法访问非静态的方法、字段、属性和事件
         * 静态方法无法通过类的实例来访问
         * 静态方法可以在一切方法中访问。
         * 2、静态构造函数
         * 类构造函数cctor。（静态构造函数不带有可见性修饰符）
         * 静态构造函数调用时机：
         * 由CLR在当前应用程序域中加载该类的元数据时调用的；
         * 必须在该类的任何实例创造之前，任何显示初始化成员初始化之后，以及
         * 任何静态成员被访问之前调用。
         * 静态构造函数在程序运行期间至少执行一次。
         * 3、 静态类(只包含静态成员，因此创建实例没有意义)
         * 由于C#编译器不为静态类定义默认构造函数，且不具有实例构造函数，所以不能创建静态类实例。
         * 另外静态类不能被继承，结构不能为静态。
         */
        
        public static void Finalizer()
        {
            System.Console.WriteLine("Thread:#{0} main thread", System.Threading.Thread.CurrentThread.ManagedThreadId);
            Memeber me = new Memeber();
            me = null;

            //对象的终结器将会在垃圾回收器收集时被调用，对象所占内存将在下一个周期释放
            System.GC.Collect();
            System.GC.WaitForPendingFinalizers();

        }
    }

    /// <summary>
    /// 嵌套类型
    /// </summary>
    public class Nest
    {
        private int m_i = 0;

        public class NestedClass
        {
            public void show(Nest Entity, int i)
            {
                // 嵌套类型可以访问包含它的类型的所有成员
                System.Console.WriteLine(Entity.m_i + i);
            }
        }
    }

    public class Memeber
    {
        private int m_i;
        public void PrivateMember(ConsoleTest.ChapterEleven.Memeber member)
        {
            //一个类的方法内部可以访问另外一个类的私有成员
            System.Console.WriteLine(member.m_i);
        }

        //类的终结器
        //类的终结器即类的析构函数
        //C#不允许直接复写Object类的Finalize方法，可以使用类似于C++析构函数的语法
        ~Memeber()
        {
            System.Console.WriteLine("Thread:#{0} Finalizer thread", System.Threading.Thread.CurrentThread.ManagedThreadId);
        }
        
    }

    public static class StaticClass
    {
        //编译器会报出：静态类不能有实例构造函数的错误
        //public StaticClass()
        //{
 
        //}
    }
}